
//  RankingViewModel.swift
//  SLQuickReader
//
//  Created by ALin on 2017/8/14.
//  Copyright © 2017年 ALin. All rights reserved.
//

import UIKit
import RxSwift
import Then
import SwiftyJSON

class RankingViewModel: BaseViewModel, BaseView {
    private weak var leftView: UITableView!
    private weak var rightView: UITableView!
    fileprivate var rankingers: [Rankinger]!
    fileprivate var selectedIndex: Int = -1
    fileprivate var gender: RankingGender = .male
    fileprivate var laseSelectedGender: RankingGender = .male
    
    fileprivate func fetchRankings(gender: RankingGender){
        let rankingObserver = BookstoreProvider
            .request(.ranking)
            .parseRankings(gender: gender)
            .catchError { _ in
                // 加载本地数据
                self.parseLocalRankings(gender: gender)
            }
        delRankings(observer: rankingObserver)
    }
    
    fileprivate func delRankings(observer: Observable<[Rankinger]>){
        leftView.dataSource = nil
        observer
            .bind(to: leftView
                .rx
                .items(cellIdentifier: "RankingMenuCell", cellType: RankingMenuCell.self))
            { row, element, cell in
                cell.menu = element.shortTitle ?? ""
            }.disposed(by: disposBag)
        
        
        
        observer.retry(3).subscribe(onNext: { [weak self] in
            guard $0.count > 0 else {
                return
            }
            
            if((self?.leftView.numberOfRows(inSection: 0) ?? 0) > 0){
                self?.rankingers = $0
                self?.leftView.reloadData()
                // 默认选中第一行
                self?.tableView(self!.leftView, didSelectRowAt: IndexPath(row: 0, section: 0))
                // 这个方法是不会调用代理的, 只会影响cell里面的方法
                self?.leftView.selectRow(at: IndexPath(row: 0, section: 0), animated: true, scrollPosition: .middle)
            }
            
            
        }).disposed(by: disposBag)
    }
    
    func bind(to view: UIView...) {
        if view.count == 3 {
            leftView = view[0] as! UITableView
            rightView = view[1] as! UITableView
            leftView
                .rx
                .setDelegate(self)
                .disposed(by: disposBag)
            
            
            guard view[2] is RankingHeader else {
                return
            }
            
            fetchRankings(gender: .male)
            
            (view[2] as! RankingHeader).clickBlock = { [weak self] tag in
                self?.laseSelectedGender = self?.gender ?? .male
                let gender: RankingGender = (tag == 0) ? .male : .female
                self?.gender = gender
                self?.delRankings(observer: (self?.parseLocalRankings(gender: gender))!)
            }
        }
    }
    
    func parseLocalRankings(gender: RankingGender) -> Observable<[Rankinger]> {
        let data = UserDefaults.standard.object(forKey: "rankingerjson")
        return Observable<[Rankinger]>.just(RankingViewModel.parseRankingData(data: data as? Data,gender: gender));
        
    }
    
    fileprivate func getRangkingDetail(rangkinger: Rankinger){
        // 因为会重复用同一个tableview, 也会被重复绑定信号
        // 所以需要每次用的时候都清除
        rightView.dataSource = nil
        // 请求第一个数据
        BookstoreProvider.request(.rankingdetail(rangkinger.totalRank!)).parse2Books(args: "ranking").catchErrorJustReturn([]).bind(to: self.rightView.rx.items(cellIdentifier: RankingCell.stringValue(), cellType: RankingCell.self))
        { row, element, cell in
            let model = RankingCellViewModel()
            model.book = element
            model.bind(to: cell)
            }.disposed(by: self.disposBag)
    }
    
    // static 和 class 的区别
    // 都可以修饰类方法
    // static: 修饰的方法是不能被子类重写的
    // class: 修饰的方法可以被子类重写
    static func parseRankingData(data: Data?, gender: RankingGender) ->  [Rankinger]{
        var result = [Rankinger]()
        guard let data = data else {
            return result
        }
        let jsonData = JSON.init(data: data)
        
        
        
        guard let arrays = jsonData[gender.rawValue].array else{
            return result
        }
        
        for dict in arrays{
            result.append(Rankinger(jsonData: dict)!)
        }
        
        return result

    }
}

extension RankingViewModel: UITableViewDelegate{
    func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
        if rankingers.count > 0 && indexPath.row < rankingers.count {
            if indexPath.row == selectedIndex && gender == laseSelectedGender {
                return
            }
            selectedIndex = indexPath.row
            getRangkingDetail(rangkinger: rankingers[indexPath.row])
        }
    }
    
}
